1   /*                        __    __  __  __    __  ___
2    *                       \  \  /  /    \  \  /  /  __/
3    *                        \  \/  /  /\  \  \/  /  /
4    *                         \____/__/  \__\____/__/.ɪᴏ
5    * ᶜᵒᵖʸʳᶦᵍʰᵗ ᵇʸ ᵛᵃᵛʳ ⁻ ˡᶦᶜᵉⁿˢᵉᵈ ᵘⁿᵈᵉʳ ᵗʰᵉ ᵃᵖᵃᶜʰᵉ ˡᶦᶜᵉⁿˢᵉ ᵛᵉʳˢᶦᵒⁿ ᵗʷᵒ ᵈᵒᵗ ᶻᵉʳᵒ
6    */
7   package io.vavr.collection;
8   
9   import io.vavr.*;
10  import io.vavr.collection.IteratorModule.ConcatIterator;
11  import io.vavr.collection.IteratorModule.DistinctIterator;
12  import io.vavr.collection.IteratorModule.GroupedIterator;
13  import io.vavr.control.Option;
14  
15  import java.math.BigDecimal;
16  import java.util.*;
17  import java.util.function.*;
18  
19  import static java.lang.Double.NEGATIVE_INFINITY;
20  import static java.lang.Double.POSITIVE_INFINITY;
21  import static java.math.RoundingMode.HALF_UP;
22  import static io.vavr.collection.IteratorModule.BigDecimalHelper.areEqual;
23  import static io.vavr.collection.IteratorModule.BigDecimalHelper.asDecimal;
24  import static io.vavr.collection.IteratorModule.EmptyIterator;
25  
26  /**
27   * {@code io.vavr.collection.Iterator} is a compositional replacement for {@code java.util.Iterator}
28   * whose purpose is to iterate <em>once</em> over a sequence of elements.
29   * <p>
30   * It is recommended to create instances using {@link AbstractIterator} in favor of {@code Iterator}.
31   * <p>
32   * <strong>Note:</strong> Iterators encapsulate mutable state.
33   * They are not meant to be used concurrently by different threads. Do not reuse Iterators, e.g. after passing to
34   * {@linkplain io.vavr.collection.List#ofAll(Iterable)}.
35   * <p>
36   * There are two abstract methods: {@code hasNext} for checking if there is a next element available,
37   * and {@code next} which removes the next element from the iterator and returns it. They can be called
38   * an arbitrary amount of times. If {@code hasNext} returns false, a call of {@code next} will throw
39   * a {@code NoSuchElementException}.
40   * <p>
41   * <strong>Caution: Other methods than {@code hasNext} and {@code next} can be called only once (exclusively).
42   * More specifically, after calling a method it cannot be guaranteed that the next call will succeed.</strong>
43   * <p>
44   * An Iterator that can be only used once because it is a traversal pointer into a collection, and not a collection
45   * itself.
46   *
47   * @param <T> Component type
48   * @author Daniel Dietrich
49   */
50  // DEV-NOTE: we prefer returning empty() over this if !hasNext() == true in order to free memory.
51  public interface Iterator<T> extends java.util.Iterator<T>, Traversable<T> {
52  
53      /**
54       * Creates an Iterator which traverses along the concatenation of the given iterables.
55       *
56       * @param iterables The iterables
57       * @param <T>       Component type.
58       * @return A new {@code io.vavr.collection.Iterator}
59       */
60      @SuppressWarnings("varargs")
61      @SafeVarargs
62      static <T> Iterator<T> concat(Iterable<? extends T>... iterables) {
63          Objects.requireNonNull(iterables, "iterables is null");
64          if (iterables.length == 0) {
65              return empty();
66          } else {
67              return new ConcatIterator<>(Stream.of(iterables).map(Iterator::ofAll).iterator());
68          }
69      }
70  
71      /**
72       * Creates an Iterator which traverses along the concatenation of the given iterables.
73       *
74       * @param iterables The iterable of iterables
75       * @param <T>       Component type.
76       * @return A new {@code io.vavr.collection.Iterator}
77       */
78      static <T> Iterator<T> concat(Iterable<? extends Iterable<? extends T>> iterables) {
79          Objects.requireNonNull(iterables, "iterables is null");
80          if (!iterables.iterator().hasNext()) {
81              return empty();
82          } else {
83              return new ConcatIterator<>(Stream.ofAll(iterables).map(Iterator::ofAll).iterator());
84          }
85      }
86  
87      /**
88       * Returns the empty Iterator.
89       *
90       * @param <T> Component type
91       * @return The empty Iterator
92       */
93      @SuppressWarnings("unchecked")
94      static <T> Iterator<T> empty() {
95          return (Iterator<T>) EmptyIterator.INSTANCE;
96      }
97  
98      /**
99       * Narrows a widened {@code Iterator<? extends T>} to {@code Iterator<T>}
100      * by performing a type-safe cast. This is eligible because immutable/read-only
101      * collections are covariant.
102      *
103      * @param iterator An {@code Iterator}.
104      * @param <T>      Component type of the {@code Iterator}.
105      * @return the given {@code iterator} instance as narrowed type {@code Iterator<T>}.
106      */
107     @SuppressWarnings("unchecked")
108     static <T> Iterator<T> narrow(Iterator<? extends T> iterator) {
109         return (Iterator<T>) iterator;
110     }
111 
112     /**
113      * Creates an Iterator which traverses one element.
114      *
115      * @param element An element
116      * @param <T>     Component type.
117      * @return A new Iterator
118      */
119     static <T> Iterator<T> of(T element) {
120         return new AbstractIterator<T>() {
121 
122             boolean hasNext = true;
123 
124             @Override
125             public boolean hasNext() {
126                 return hasNext;
127             }
128 
129             @Override
130             public T getNext() {
131                 hasNext = false;
132                 return element;
133             }
134         };
135     }
136 
137     /**
138      * Creates an Iterator which traverses the given elements.
139      *
140      * @param elements Zero or more elements
141      * @param <T>      Component type
142      * @return A new Iterator
143      */
144     @SafeVarargs
145     static <T> Iterator<T> of(T... elements) {
146         Objects.requireNonNull(elements, "elements is null");
147         if (elements.length == 0) {
148             return empty();
149         } else {
150             return new AbstractIterator<T>() {
151 
152                 int index = 0;
153 
154                 @Override
155                 public boolean hasNext() {
156                     return index < elements.length;
157                 }
158 
159                 @Override
160                 public T getNext() {
161                     return elements[index++];
162                 }
163             };
164         }
165     }
166 
167     /**
168      * Creates an Iterator based on the given Iterable. This is a convenience method for
169      * {@code Iterator.ofAll(iterable.iterator()}.
170      *
171      * @param iterable A {@link Iterable}
172      * @param <T>      Component type.
173      * @return A new {@code io.vavr.collection.Iterator}
174      */
175     @SuppressWarnings("unchecked")
176     static <T> Iterator<T> ofAll(Iterable<? extends T> iterable) {
177         Objects.requireNonNull(iterable, "iterable is null");
178         if (iterable instanceof Iterator) {
179             return (Iterator<T>) iterable;
180         } else {
181             return ofAll(iterable.iterator());
182         }
183     }
184 
185     /**
186      * Creates an Iterator based on the given Iterator by
187      * delegating calls of {@code hasNext()} and {@code next()} to it.
188      *
189      * @param iterator A {@link java.util.Iterator}
190      * @param <T>      Component type.
191      * @return A new {@code io.vavr.collection.Iterator}
192      */
193     @SuppressWarnings("unchecked")
194     static <T> Iterator<T> ofAll(java.util.Iterator<? extends T> iterator) {
195         Objects.requireNonNull(iterator, "iterator is null");
196         if (iterator instanceof Iterator) {
197             return (Iterator<T>) iterator;
198         } else {
199             return new AbstractIterator<T>() {
200 
201                 @Override
202                 public boolean hasNext() {
203                     return iterator.hasNext();
204                 }
205 
206                 @Override
207                 public T getNext() {
208                     return iterator.next();
209                 }
210             };
211         }
212     }
213 
214     /**
215      * Creates an Iterator from boolean values.
216      *
217      * @param elements boolean values
218      * @return A new Iterator of Boolean values
219      * @throws NullPointerException if elements is null
220      */
221     static Iterator<Boolean> ofAll(boolean... elements) {
222         Objects.requireNonNull(elements, "elements is null");
223         return new AbstractIterator<Boolean>() {
224             int i = 0;
225 
226             @Override
227             public boolean hasNext() {
228                 return i < elements.length;
229             }
230 
231             @Override
232             public Boolean getNext() {
233                 return elements[i++];
234             }
235         };
236     }
237 
238     /**
239      * Creates an Iterator from byte values.
240      *
241      * @param elements byte values
242      * @return A new Iterator of Byte values
243      * @throws NullPointerException if elements is null
244      */
245     static Iterator<Byte> ofAll(byte... elements) {
246         Objects.requireNonNull(elements, "elements is null");
247         return new AbstractIterator<Byte>() {
248             int i = 0;
249 
250             @Override
251             public boolean hasNext() {
252                 return i < elements.length;
253             }
254 
255             @Override
256             public Byte getNext() {
257                 return elements[i++];
258             }
259         };
260     }
261 
262     /**
263      * Creates an Iterator from char values.
264      *
265      * @param elements char values
266      * @return A new Iterator of Character values
267      * @throws NullPointerException if elements is null
268      */
269     static Iterator<Character> ofAll(char... elements) {
270         Objects.requireNonNull(elements, "elements is null");
271         return new AbstractIterator<Character>() {
272             int i = 0;
273 
274             @Override
275             public boolean hasNext() {
276                 return i < elements.length;
277             }
278 
279             @Override
280             public Character getNext() {
281                 return elements[i++];
282             }
283         };
284     }
285 
286     /**
287      * Creates ann Iterator from double values.
288      *
289      * @param elements double values
290      * @return A new Iterator of Double values
291      * @throws NullPointerException if elements is null
292      */
293     static Iterator<Double> ofAll(double... elements) {
294         Objects.requireNonNull(elements, "elements is null");
295         return new AbstractIterator<Double>() {
296             int i = 0;
297 
298             @Override
299             public boolean hasNext() {
300                 return i < elements.length;
301             }
302 
303             @Override
304             public Double getNext() {
305                 return elements[i++];
306             }
307         };
308     }
309 
310     /**
311      * Creates an Iterator from float values.
312      *
313      * @param elements float values
314      * @return A new Iterator of Float values
315      * @throws NullPointerException if elements is null
316      */
317     static Iterator<Float> ofAll(float... elements) {
318         Objects.requireNonNull(elements, "elements is null");
319         return new AbstractIterator<Float>() {
320             int i = 0;
321 
322             @Override
323             public boolean hasNext() {
324                 return i < elements.length;
325             }
326 
327             @Override
328             public Float getNext() {
329                 return elements[i++];
330             }
331         };
332     }
333 
334     /**
335      * Creates an Iterator from int values.
336      *
337      * @param elements int values
338      * @return A new Iterator of Integer values
339      * @throws NullPointerException if elements is null
340      */
341     static Iterator<Integer> ofAll(int... elements) {
342         Objects.requireNonNull(elements, "elements is null");
343         return new AbstractIterator<Integer>() {
344             int i = 0;
345 
346             @Override
347             public boolean hasNext() {
348                 return i < elements.length;
349             }
350 
351             @Override
352             public Integer getNext() {
353                 return elements[i++];
354             }
355         };
356     }
357 
358     /**
359      * Creates an Iterator from long values.
360      *
361      * @param elements long values
362      * @return A new Iterator of Long values
363      * @throws NullPointerException if elements is null
364      */
365     static Iterator<Long> ofAll(long... elements) {
366         Objects.requireNonNull(elements, "elements is null");
367         return new AbstractIterator<Long>() {
368             int i = 0;
369 
370             @Override
371             public boolean hasNext() {
372                 return i < elements.length;
373             }
374 
375             @Override
376             public Long getNext() {
377                 return elements[i++];
378             }
379         };
380     }
381 
382     /**
383      * Creates an Iterator from short values.
384      *
385      * @param elements short values
386      * @return A new Iterator of Short values
387      * @throws NullPointerException if elements is null
388      */
389     static Iterator<Short> ofAll(short... elements) {
390         Objects.requireNonNull(elements, "elements is null");
391         return new AbstractIterator<Short>() {
392             int i = 0;
393 
394             @Override
395             public boolean hasNext() {
396                 return i < elements.length;
397             }
398 
399             @Override
400             public Short getNext() {
401                 return elements[i++];
402             }
403         };
404     }
405 
406     /**
407      * Returns an Iterator on a sequence of {@code n} values of a given Function {@code f}
408      * over a range of integer values from 0 to {@code n - 1}.
409      *
410      * @param <T> Component type of the Iterator
411      * @param n   The number of elements
412      * @param f   The Function computing element values
413      * @return An Iterator on a sequence of elements {@code f(0),f(1), ..., f(n - 1)}
414      * @throws NullPointerException if {@code f} is null
415      */
416     static <T> Iterator<T> tabulate(int n, Function<? super Integer, ? extends T> f) {
417         Objects.requireNonNull(f, "f is null");
418         return io.vavr.collection.Collections.tabulate(n, f);
419     }
420 
421     /**
422      * Returns an Iterator on a sequence of {@code n} values supplied by a given Supplier {@code s}.
423      *
424      * @param <T> Component type of the Iterator
425      * @param n   The number of elements
426      * @param s   The Supplier computing element values
427      * @return An iterator on a sequence of {@code n} elements, where each element contains the result supplied by {@code s}.
428      * @throws NullPointerException if {@code s} is null
429      */
430     static <T> Iterator<T> fill(int n, Supplier<? extends T> s) {
431         Objects.requireNonNull(s, "s is null");
432         return io.vavr.collection.Collections.fill(n, s);
433     }
434 
435     /**
436      * Creates an Iterator of characters starting from {@code from}, extending to {@code toExclusive - 1}.
437      * <p>
438      * Examples:
439      * <pre>
440      * <code>
441      * Iterator.range('a', 'c')  // = ('a', 'b')
442      * Iterator.range('c', 'a')  // = ()
443      * </code>
444      * </pre>
445      *
446      * @param from        the first character
447      * @param toExclusive the successor of the last character
448      * @return a range of characters as specified or the empty range if {@code from >= toExclusive}
449      */
450     static Iterator<Character> range(char from, char toExclusive) {
451         return rangeBy(from, toExclusive, 1);
452     }
453 
454     /**
455      * Creates an Iterator of characters starting from {@code from}, extending to {@code toExclusive - 1},
456      * with {@code step}.
457      * <p>
458      * Examples:
459      * <pre>
460      * <code>
461      * Iterator.rangeBy('a', 'c', 1)  // = ('a', 'b')
462      * Iterator.rangeBy('a', 'd', 2)  // = ('a', 'c')
463      * Iterator.rangeBy('d', 'a', -2) // = ('d', 'b')
464      * Iterator.rangeBy('d', 'a', 2)  // = ()
465      * </code>
466      * </pre>
467      *
468      * @param from        the first character
469      * @param toExclusive the successor of the last character if step &gt; 0, the predecessor of the last character if step &lt; 0
470      * @param step        the step
471      * @return a range of characters as specified or the empty range if {@code signum(step) == signum(from - toExclusive)}.
472      * @throws IllegalArgumentException if {@code step} is zero
473      */
474     static Iterator<Character> rangeBy(char from, char toExclusive, int step) {
475         return rangeBy((int) from, (int) toExclusive, step).map(i -> (char) i.shortValue());
476     }
477 
478     @GwtIncompatible("BigDecimalHelper is GwtIncompatible")
479     static Iterator<Double> rangeBy(double from, double toExclusive, double step) {
480         final BigDecimal fromDecimal = asDecimal(from), toDecimal = asDecimal(toExclusive), stepDecimal = asDecimal(step);
481         return rangeBy(fromDecimal, toDecimal, stepDecimal).map(BigDecimal::doubleValue);
482     }
483 
484     static Iterator<BigDecimal> rangeBy(BigDecimal from, BigDecimal toExclusive, BigDecimal step) {
485         if (step.signum() == 0) {
486             throw new IllegalArgumentException("step cannot be 0");
487         } else if (areEqual(from, toExclusive) || step.signum() == from.subtract(toExclusive).signum()) {
488             return empty();
489         } else {
490             if (step.signum() > 0) {
491                 return new AbstractIterator<BigDecimal>() {
492                     BigDecimal i = from;
493 
494                     @Override
495                     public boolean hasNext() {
496                         return i.compareTo(toExclusive) < 0;
497                     }
498 
499                     @Override
500                     public BigDecimal getNext() {
501                         final BigDecimal next = this.i;
502                         this.i = next.add(step);
503                         return next;
504                     }
505                 };
506             } else {
507                 return new AbstractIterator<BigDecimal>() {
508                     BigDecimal i = from;
509 
510                     @Override
511                     public boolean hasNext() {
512                         return i.compareTo(toExclusive) > 0;
513                     }
514 
515                     @Override
516                     public BigDecimal getNext() {
517                         final BigDecimal next = this.i;
518                         this.i = next.add(step);
519                         return next;
520                     }
521                 };
522             }
523         }
524     }
525 
526     /**
527      * Creates an Iterator of int numbers starting from {@code from}, extending to {@code toExclusive - 1}.
528      * <p>
529      * Examples:
530      * <pre>
531      * <code>
532      * Iterator.range(0, 0)  // = ()
533      * Iterator.range(2, 0)  // = ()
534      * Iterator.range(-2, 2) // = (-2, -1, 0, 1)
535      * </code>
536      * </pre>
537      *
538      * @param from        the first number
539      * @param toExclusive the last number + 1
540      * @return a range of int values as specified or the empty range if {@code from >= toExclusive}
541      */
542     static Iterator<Integer> range(int from, int toExclusive) {
543         return rangeBy(from, toExclusive, 1);
544     }
545 
546     /**
547      * Creates an Iterator of int numbers starting from {@code from}, extending to {@code toExclusive - 1},
548      * with {@code step}.
549      * <p>
550      * Examples:
551      * <pre>
552      * <code>
553      * Iterator.rangeBy(1, 3, 1)  // = (1, 2)
554      * Iterator.rangeBy(1, 4, 2)  // = (1, 3)
555      * Iterator.rangeBy(4, 1, -2) // = (4, 2)
556      * Iterator.rangeBy(4, 1, 2)  // = ()
557      * </code>
558      * </pre>
559      *
560      * @param from        the first number
561      * @param toExclusive the last number + 1 if step &gt; 0, the last number - 1 if step &lt; 0
562      * @param step        the step
563      * @return a range of long values as specified or the empty range if {@code (from == toExclusive) || (step * (from - toExclusive) > 0)}.
564      * @throws IllegalArgumentException if {@code step} is zero
565      */
566     static Iterator<Integer> rangeBy(int from, int toExclusive, int step) {
567         final int toInclusive = toExclusive - (step > 0 ? 1 : -1);
568         return rangeClosedBy(from, toInclusive, step);
569     }
570 
571     /**
572      * Creates an Iterator of long numbers starting from {@code from}, extending to {@code toExclusive - 1}.
573      * <p>
574      * Examples:
575      * <pre>
576      * <code>
577      * Iterator.range(0L, 0L)  // = ()
578      * Iterator.range(2L, 0L)  // = ()
579      * Iterator.range(-2L, 2L) // = (-2L, -1L, 0L, 1L)
580      * </code>
581      * </pre>
582      *
583      * @param from        the first number
584      * @param toExclusive the last number + 1
585      * @return a range of long values as specified or the empty range if {@code from >= toExclusive}
586      */
587     static Iterator<Long> range(long from, long toExclusive) {
588         return rangeBy(from, toExclusive, 1);
589     }
590 
591     /**
592      * Creates an Iterator of long numbers starting from {@code from}, extending to {@code toExclusive - 1},
593      * with {@code step}.
594      * <p>
595      * Examples:
596      * <pre>
597      * <code>
598      * Iterator.rangeBy(1L, 3L, 1L)  // = (1L, 2L)
599      * Iterator.rangeBy(1L, 4L, 2L)  // = (1L, 3L)
600      * Iterator.rangeBy(4L, 1L, -2L) // = (4L, 2L)
601      * Iterator.rangeBy(4L, 1L, 2L)  // = ()
602      * </code>
603      * </pre>
604      *
605      * @param from        the first number
606      * @param toExclusive the last number + 1 if step &gt; 0, the last number - 1 if step &lt; 0
607      * @param step        the step
608      * @return a range of long values as specified or the empty range if {@code (from == toExclusive) || (step * (from - toExclusive) > 0)}.
609      * @throws IllegalArgumentException if {@code step} is zero
610      */
611     static Iterator<Long> rangeBy(long from, long toExclusive, long step) {
612         final long toInclusive = toExclusive - (step > 0 ? 1 : -1);
613         return rangeClosedBy(from, toInclusive, step);
614     }
615 
616     /**
617      * Creates an Iterator of characters starting from {@code from}, extending to {@code toInclusive}.
618      * <p>
619      * Examples:
620      * <pre>
621      * <code>
622      * Iterator.rangeClosed('a', 'c')  // = ('a', 'b', 'c')
623      * Iterator.rangeClosed('c', 'a')  // = ()
624      * </code>
625      * </pre>
626      *
627      * @param from        the first character
628      * @param toInclusive the last character
629      * @return a range of characters as specified or the empty range if {@code from > toInclusive}
630      */
631     static Iterator<Character> rangeClosed(char from, char toInclusive) {
632         return rangeClosedBy(from, toInclusive, 1);
633     }
634 
635     /**
636      * Creates an Iterator of characters starting from {@code from}, extending to {@code toInclusive},
637      * with {@code step}.
638      * <p>
639      * Examples:
640      * <pre>
641      * <code>
642      * Iterator.rangeClosedBy('a', 'c', 1)  // = ('a', 'b', 'c')
643      * Iterator.rangeClosedBy('a', 'd', 2)  // = ('a', 'c')
644      * Iterator.rangeClosedBy('d', 'a', -2) // = ('d', 'b')
645      * Iterator.rangeClosedBy('d', 'a', 2)  // = ()
646      * </code>
647      * </pre>
648      *
649      * @param from        the first character
650      * @param toInclusive the last character
651      * @param step        the step
652      * @return a range of characters as specified or the empty range if {@code signum(step) == signum(from - toInclusive)}.
653      * @throws IllegalArgumentException if {@code step} is zero
654      */
655     static Iterator<Character> rangeClosedBy(char from, char toInclusive, int step) {
656         return rangeClosedBy((int) from, (int) toInclusive, step).map(i -> (char) i.shortValue());
657     }
658 
659     @GwtIncompatible
660     static Iterator<Double> rangeClosedBy(double from, double toInclusive, double step) {
661         if (from == toInclusive) {
662             return of(from);
663         }
664 
665         final double toExclusive = (step > 0) ? Math.nextUp(toInclusive) : Math.nextDown(toInclusive);
666         return rangeBy(from, toExclusive, step);
667     }
668 
669     /**
670      * Creates an Iterator of int numbers starting from {@code from}, extending to {@code toInclusive}.
671      * <p>
672      * Examples:
673      * <pre>
674      * <code>
675      * Iterator.rangeClosed(0, 0)  // = (0)
676      * Iterator.rangeClosed(2, 0)  // = ()
677      * Iterator.rangeClosed(-2, 2) // = (-2, -1, 0, 1, 2)
678      * </code>
679      * </pre>
680      *
681      * @param from        the first number
682      * @param toInclusive the last number
683      * @return a range of int values as specified or the empty range if {@code from > toInclusive}
684      */
685     static Iterator<Integer> rangeClosed(int from, int toInclusive) {
686         return rangeClosedBy(from, toInclusive, 1);
687     }
688 
689     /**
690      * Creates an Iterator of int numbers starting from {@code from}, extending to {@code toInclusive},
691      * with {@code step}.
692      * <p>
693      * Examples:
694      * <pre>
695      * <code>
696      * Iterator.rangeClosedBy(1, 3, 1)  // = (1, 2, 3)
697      * Iterator.rangeClosedBy(1, 4, 2)  // = (1, 3)
698      * Iterator.rangeClosedBy(4, 1, -2) // = (4, 2)
699      * Iterator.rangeClosedBy(4, 1, 2)  // = ()
700      * </code>
701      * </pre>
702      *
703      * @param from        the first number
704      * @param toInclusive the last number
705      * @param step        the step
706      * @return a range of int values as specified or the empty range if {@code signum(step) == signum(from - toInclusive)}.
707      * @throws IllegalArgumentException if {@code step} is zero
708      */
709     static Iterator<Integer> rangeClosedBy(int from, int toInclusive, int step) {
710         if (step == 0) {
711             throw new IllegalArgumentException("step cannot be 0");
712         } else if (from == toInclusive) {
713             return of(from);
714         } else if (Integer.signum(step) == Integer.signum(from - toInclusive)) {
715             return empty();
716         } else {
717             final int end = toInclusive - step;
718             if (step > 0) {
719                 return new AbstractIterator<Integer>() {
720                     int i = from - step;
721 
722                     @Override
723                     public boolean hasNext() {
724                         return i <= end;
725                     }
726 
727                     @Override
728                     public Integer getNext() {
729                         return i += step;
730                     }
731                 };
732             } else {
733                 return new AbstractIterator<Integer>() {
734                     int i = from - step;
735 
736                     @Override
737                     public boolean hasNext() {
738                         return i >= end;
739                     }
740 
741                     @Override
742                     public Integer getNext() {
743                         return i += step;
744                     }
745                 };
746             }
747         }
748     }
749 
750     /**
751      * Creates an Iterator of long numbers starting from {@code from}, extending to {@code toInclusive}.
752      * <p>
753      * Examples:
754      * <pre>
755      * <code>
756      * Iterator.rangeClosed(0L, 0L)  // = (0L)
757      * Iterator.rangeClosed(2L, 0L)  // = ()
758      * Iterator.rangeClosed(-2L, 2L) // = (-2L, -1L, 0L, 1L, 2L)
759      * </code>
760      * </pre>
761      *
762      * @param from        the first number
763      * @param toInclusive the last number
764      * @return a range of long values as specified or the empty range if {@code from > toInclusive}
765      */
766     static Iterator<Long> rangeClosed(long from, long toInclusive) {
767         return rangeClosedBy(from, toInclusive, 1L);
768     }
769 
770     /**
771      * Creates an Iterator of long numbers starting from {@code from}, extending to {@code toInclusive},
772      * with {@code step}.
773      * <p>
774      * Examples:
775      * <pre>
776      * <code>
777      * Iterator.rangeClosedBy(1L, 3L, 1L)  // = (1L, 2L, 3L)
778      * Iterator.rangeClosedBy(1L, 4L, 2L)  // = (1L, 3L)
779      * Iterator.rangeClosedBy(4L, 1L, -2L) // = (4L, 2L)
780      * Iterator.rangeClosedBy(4L, 1L, 2L)  // = ()
781      * </code>
782      * </pre>
783      *
784      * @param from        the first number
785      * @param toInclusive the last number
786      * @param step        the step
787      * @return a range of int values as specified or the empty range if {@code signum(step) == signum(from - toInclusive)}.
788      * @throws IllegalArgumentException if {@code step} is zero
789      */
790     static Iterator<Long> rangeClosedBy(long from, long toInclusive, long step) {
791         if (step == 0) {
792             throw new IllegalArgumentException("step cannot be 0");
793         } else if (from == toInclusive) {
794             return of(from);
795         } else if (Long.signum(step) == Long.signum(from - toInclusive)) {
796             return empty();
797         } else {
798             final long end = toInclusive - step;
799             if (step > 0) {
800                 return new AbstractIterator<Long>() {
801                     long i = from - step;
802 
803                     @Override
804                     public boolean hasNext() {
805                         return i <= end;
806                     }
807 
808                     @Override
809                     public Long getNext() {
810                         return i += step;
811                     }
812                 };
813             } else {
814                 return new AbstractIterator<Long>() {
815                     long i = from - step;
816 
817                     @Override
818                     public boolean hasNext() {
819                         return i >= end;
820                     }
821 
822                     @Override
823                     public Long getNext() {
824                         return i += step;
825                     }
826                 };
827 
828             }
829         }
830     }
831 
832     /**
833      * Returns an infinite iterator of int values starting from {@code value}.
834      * <p>
835      * The {@code Iterator} extends to {@code Integer.MIN_VALUE} when passing {@code Integer.MAX_VALUE}.
836      *
837      * @param value a start int value
838      * @return a new {@code Iterator} of int values starting from {@code from}
839      */
840     static Iterator<Integer> from(int value) {
841         return new AbstractIterator<Integer>() {
842             private int next = value;
843 
844             @Override
845             public boolean hasNext() {
846                 return true;
847             }
848 
849             @Override
850             public Integer getNext() {
851                 return next++;
852             }
853         };
854     }
855 
856     /**
857      * Returns an infinite iterator of int values starting from {@code value} and spaced by {@code step}.
858      * <p>
859      * The {@code Iterator} extends to {@code Integer.MIN_VALUE} when passing {@code Integer.MAX_VALUE}.
860      *
861      * @param value a start int value
862      * @param step  the step by which to advance on each iteration
863      * @return a new {@code Iterator} of int values starting from {@code from}
864      */
865     static Iterator<Integer> from(int value, int step) {
866         return new AbstractIterator<Integer>() {
867             private int next = value;
868 
869             @Override
870             public boolean hasNext() {
871                 return true;
872             }
873 
874             @Override
875             public Integer getNext() {
876                 final int result = next;
877                 next += step;
878                 return result;
879             }
880         };
881     }
882 
883     /**
884      * Returns an infinite iterator of long values starting from {@code value}.
885      * <p>
886      * The {@code Iterator} extends to {@code Long.MIN_VALUE} when passing {@code Long.MAX_VALUE}.
887      *
888      * @param value a start long value
889      * @return a new {@code Iterator} of long values starting from {@code from}
890      */
891     static Iterator<Long> from(long value) {
892         return new AbstractIterator<Long>() {
893             private long next = value;
894 
895             @Override
896             public boolean hasNext() {
897                 return true;
898             }
899 
900             @Override
901             public Long getNext() {
902                 return next++;
903             }
904         };
905     }
906 
907     /**
908      * Returns an infinite iterator of long values starting from {@code value} and spaced by {@code step}.
909      * <p>
910      * The {@code Iterator} extends to {@code Long.MIN_VALUE} when passing {@code Long.MAX_VALUE}.
911      *
912      * @param value a start long value
913      * @param step  the step by which to advance on each iteration
914      * @return a new {@code Iterator} of long values starting from {@code from}
915      */
916     static Iterator<Long> from(long value, long step) {
917         return new AbstractIterator<Long>() {
918             private long next = value;
919 
920             @Override
921             public boolean hasNext() {
922                 return true;
923             }
924 
925             @Override
926             public Long getNext() {
927                 final long result = next;
928                 next += step;
929                 return result;
930             }
931         };
932     }
933 
934     /**
935      * Generates an infinite iterator using a value Supplier.
936      *
937      * @param supplier A Supplier of iterator values
938      * @param <T>      value type
939      * @return A new {@code Iterator}
940      */
941     static <T> Iterator<T> continually(Supplier<? extends T> supplier) {
942         Objects.requireNonNull(supplier, "supplier is null");
943         return new AbstractIterator<T>() {
944             @Override
945             public boolean hasNext() {
946                 return true;
947             }
948 
949             @Override
950             public T getNext() {
951                 return supplier.get();
952             }
953         };
954     }
955 
956     /**
957      * Generates an infinite iterator using a function to calculate the next value
958      * based on the previous.
959      *
960      * @param seed The first value in the iterator
961      * @param f    A function to calculate the next value based on the previous
962      * @param <T>  value type
963      * @return A new {@code Iterator}
964      */
965     static <T> Iterator<T> iterate(T seed, Function<? super T, ? extends T> f) {
966         Objects.requireNonNull(f, "f is null");
967         return new AbstractIterator<T>() {
968             Function<? super T, ? extends T> nextFunc = s -> {
969                 nextFunc = f;
970                 return seed;
971             };
972             T current = null;
973 
974             @Override
975             public boolean hasNext() {
976                 return true;
977             }
978 
979             @Override
980             public T getNext() {
981                 current = nextFunc.apply(current);
982                 return current;
983             }
984         };
985     }
986 
987     /**
988      * Creates an infinite iterator returning the given element.
989      *
990      * @param t   An element
991      * @param <T> Element type
992      * @return A new Iterator containing infinite {@code t}'s.
993      */
994     static <T> Iterator<T> continually(T t) {
995         return new AbstractIterator<T>() {
996             @Override
997             public boolean hasNext() {
998                 return true;
999             }
1000 
1001             @Override
1002             public T getNext() {
1003                 return t;
1004             }
1005         };
1006     }
1007 
1008     // -- Additional methods of Iterator
1009 
1010     @Override
1011     default <R> Iterator<R> collect(PartialFunction<? super T, ? extends R> partialFunction) {
1012         Objects.requireNonNull(partialFunction, "partialFunction is null");
1013         return filter(partialFunction::isDefinedAt).map(partialFunction::apply);
1014     }
1015 
1016     // DEV-NOTE: cannot use arg Iterable, it would be ambiguous
1017     default Iterator<T> concat(java.util.Iterator<? extends T> that) {
1018         Objects.requireNonNull(that, "that is null");
1019         if (!that.hasNext()) {
1020             return this;
1021         } else if (!hasNext()) {
1022             return ofAll(that);
1023         } else {
1024             return concat(this, ofAll(that));
1025         }
1026     }
1027 
1028     /**
1029      * Inserts an element between all elements of this Iterator.
1030      *
1031      * @param element An element.
1032      * @return an interspersed version of this
1033      */
1034     default Iterator<T> intersperse(T element) {
1035         if (!hasNext()) {
1036             return empty();
1037         } else {
1038             final Iterator<T> that = this;
1039             return new AbstractIterator<T>() {
1040 
1041                 boolean insertElement = false;
1042 
1043                 @Override
1044                 public boolean hasNext() {
1045                     return that.hasNext();
1046                 }
1047 
1048                 @Override
1049                 public T getNext() {
1050                     if (insertElement) {
1051                         insertElement = false;
1052                         return element;
1053                     } else {
1054                         insertElement = true;
1055                         return that.next();
1056                     }
1057                 }
1058             };
1059         }
1060     }
1061 
1062     /**
1063      * Transforms this {@code Iterator}.
1064      *
1065      * @param f   A transformation
1066      * @param <U> Type of transformation result
1067      * @return An instance of type {@code U}
1068      * @throws NullPointerException if {@code f} is null
1069      */
1070     default <U> U transform(Function<? super Iterator<T>, ? extends U> f) {
1071         Objects.requireNonNull(f, "f is null");
1072         return f.apply(this);
1073     }
1074 
1075     @Override
1076     default <U> Iterator<Tuple2<T, U>> zip(Iterable<? extends U> that) {
1077         return zipWith(that, Tuple::of);
1078     }
1079 
1080     @Override
1081     default <U, R> Iterator<R> zipWith(Iterable<? extends U> that, BiFunction<? super T, ? super U, ? extends R> mapper) {
1082         Objects.requireNonNull(that, "that is null");
1083         Objects.requireNonNull(mapper, "mapper is null");
1084         if (isEmpty()) {
1085             return empty();
1086         } else {
1087             final Iterator<T> it1 = this;
1088             final java.util.Iterator<? extends U> it2 = that.iterator();
1089             return new AbstractIterator<R>() {
1090                 @Override
1091                 public boolean hasNext() {
1092                     return it1.hasNext() && it2.hasNext();
1093                 }
1094 
1095                 @Override
1096                 public R getNext() {
1097                     return mapper.apply(it1.next(), it2.next());
1098                 }
1099             };
1100         }
1101     }
1102 
1103     @Override
1104     default <U> Iterator<Tuple2<T, U>> zipAll(Iterable<? extends U> that, T thisElem, U thatElem) {
1105         Objects.requireNonNull(that, "that is null");
1106         final java.util.Iterator<? extends U> thatIt = that.iterator();
1107         if (isEmpty() && !thatIt.hasNext()) {
1108             return empty();
1109         } else {
1110             final Iterator<T> thisIt = this;
1111             return new AbstractIterator<Tuple2<T, U>>() {
1112                 @Override
1113                 public boolean hasNext() {
1114                     return thisIt.hasNext() || thatIt.hasNext();
1115                 }
1116 
1117                 @Override
1118                 public Tuple2<T, U> getNext() {
1119                     final T v1 = thisIt.hasNext() ? thisIt.next() : thisElem;
1120                     final U v2 = thatIt.hasNext() ? thatIt.next() : thatElem;
1121                     return Tuple.of(v1, v2);
1122                 }
1123             };
1124         }
1125     }
1126 
1127     @Override
1128     default Iterator<Tuple2<T, Integer>> zipWithIndex() {
1129         return zipWithIndex(Tuple::of);
1130     }
1131 
1132     @Override
1133     default <U> Iterator<U> zipWithIndex(BiFunction<? super T, ? super Integer, ? extends U> mapper) {
1134         Objects.requireNonNull(mapper, "mapper is null");
1135         if (isEmpty()) {
1136             return empty();
1137         } else {
1138             final Iterator<T> it1 = this;
1139             return new AbstractIterator<U>() {
1140                 private int index = 0;
1141 
1142                 @Override
1143                 public boolean hasNext() {
1144                     return it1.hasNext();
1145                 }
1146 
1147                 @Override
1148                 public U getNext() {
1149                     return mapper.apply(it1.next(), index++);
1150                 }
1151             };
1152         }
1153     }
1154 
1155     @Override
1156     default <T1, T2> Tuple2<Iterator<T1>, Iterator<T2>> unzip(
1157             Function<? super T, Tuple2<? extends T1, ? extends T2>> unzipper) {
1158         Objects.requireNonNull(unzipper, "unzipper is null");
1159         if (!hasNext()) {
1160             return Tuple.of(empty(), empty());
1161         } else {
1162             final Stream<Tuple2<? extends T1, ? extends T2>> source = Stream.ofAll(this.map(unzipper));
1163             return Tuple.of(source.map(t -> (T1) t._1).iterator(), source.map(t -> (T2) t._2).iterator());
1164         }
1165     }
1166 
1167     @Override
1168     default <T1, T2, T3> Tuple3<Iterator<T1>, Iterator<T2>, Iterator<T3>> unzip3(
1169             Function<? super T, Tuple3<? extends T1, ? extends T2, ? extends T3>> unzipper) {
1170         Objects.requireNonNull(unzipper, "unzipper is null");
1171         if (!hasNext()) {
1172             return Tuple.of(empty(), empty(), empty());
1173         } else {
1174             final Stream<Tuple3<? extends T1, ? extends T2, ? extends T3>> source = Stream.ofAll(this.map(unzipper));
1175             return Tuple.of(source.map(t -> (T1) t._1).iterator(), source.map(t -> (T2) t._2).iterator(), source.map(t -> (T3) t._3).iterator());
1176         }
1177     }
1178 
1179     /**
1180      * Creates an iterator from a seed value and a function.
1181      * The function takes the seed at first.
1182      * The function should return {@code None} when it's
1183      * done generating elements, otherwise {@code Some} {@code Tuple}
1184      * of the value to add to the resulting iterator and
1185      * the element for the next call.
1186      * <p>
1187      * Example:
1188      * <pre>
1189      * <code>
1190      * Iterator.unfold(10, x -&gt; x == 0
1191      *                 ? Option.none()
1192      *                 : Option.of(new Tuple2&lt;&gt;(x-1, x)));
1193      * // List(1, 2, 3, 4, 5, 6, 7, 8, 9, 10))
1194      * </code>
1195      * </pre>
1196      *
1197      * @param <T>  type of seeds and unfolded values
1198      * @param seed the start value for the iteration
1199      * @param f    the function to get the next step of the iteration
1200      * @return a list with the values built up by the iteration
1201      * @throws NullPointerException if {@code f} is null
1202      */
1203     static <T> Iterator<T> unfold(T seed, Function<? super T, Option<Tuple2<? extends T, ? extends T>>> f) {
1204         return unfoldLeft(seed, f);
1205     }
1206 
1207     /**
1208      * Creates an iterator from a seed value and a function.
1209      * The function takes the seed at first.
1210      * The function should return {@code None} when it's
1211      * done generating elements, otherwise {@code Some} {@code Tuple}
1212      * of the value to add to the resulting iterator and
1213      * the element for the next call.
1214      * <p>
1215      * Example:
1216      * <pre>
1217      * <code>
1218      * Iterator.unfoldLeft(10, x -&gt; x == 0
1219      *                    ? Option.none()
1220      *                    : Option.of(new Tuple2&lt;&gt;(x-1, x)));
1221      * // List(1, 2, 3, 4, 5, 6, 7, 8, 9, 10))
1222      * </code>
1223      * </pre>
1224      *
1225      * @param <T>  type of seeds
1226      * @param <U>  type of unfolded values
1227      * @param seed the start value for the iteration
1228      * @param f    the function to get the next step of the iteration
1229      * @return a list with the values built up by the iteration
1230      * @throws NullPointerException if {@code f} is null
1231      */
1232     static <T, U> Iterator<U> unfoldLeft(T seed, Function<? super T, Option<Tuple2<? extends T, ? extends U>>> f) {
1233         Objects.requireNonNull(f, "f is null");
1234         return Stream.<U> ofAll(
1235                 unfoldRight(seed, f.andThen(tupleOpt -> tupleOpt.map(t -> Tuple.of(t._2, t._1)))))
1236                 .reverse().iterator();
1237     }
1238 
1239     /**
1240      * Creates an iterator from a seed value and a function.
1241      * The function takes the seed at first.
1242      * The function should return {@code None} when it's
1243      * done generating elements, otherwise {@code Some} {@code Tuple}
1244      * of the element for the next call and the value to add to the
1245      * resulting iterator.
1246      * <p>
1247      * Example:
1248      * <pre>
1249      * <code>
1250      * Iterator.unfoldRight(10, x -&gt; x == 0
1251      *             ? Option.none()
1252      *             : Option.of(new Tuple2&lt;&gt;(x, x-1)));
1253      * // List(10, 9, 8, 7, 6, 5, 4, 3, 2, 1))
1254      * </code>
1255      * </pre>
1256      *
1257      * @param <T>  type of seeds
1258      * @param <U>  type of unfolded values
1259      * @param seed the start value for the iteration
1260      * @param f    the function to get the next step of the iteration
1261      * @return a list with the values built up by the iteration
1262      * @throws NullPointerException if {@code f} is null
1263      */
1264     static <T, U> Iterator<U> unfoldRight(T seed, Function<? super T, Option<Tuple2<? extends U, ? extends T>>> f) {
1265         Objects.requireNonNull(f, "the unfold iterating function is null");
1266         return new AbstractIterator<U>() {
1267             private Option<Tuple2<? extends U, ? extends T>> nextVal = f.apply(seed);
1268 
1269             @Override
1270             public boolean hasNext() {
1271                 return nextVal.isDefined();
1272             }
1273 
1274             @Override
1275             public U getNext() {
1276                 final U result = nextVal.get()._1;
1277                 nextVal = f.apply(nextVal.get()._2);
1278                 return result;
1279             }
1280         };
1281     }
1282 
1283     // -- Overridden methods of Traversable
1284 
1285     @Override
1286     default Iterator<T> distinct() {
1287         if (!hasNext()) {
1288             return empty();
1289         } else {
1290             return new DistinctIterator<>(this, io.vavr.collection.HashSet.empty(), Function.identity());
1291         }
1292     }
1293 
1294     @Override
1295     default Iterator<T> distinctBy(Comparator<? super T> comparator) {
1296         Objects.requireNonNull(comparator, "comparator is null");
1297         if (!hasNext()) {
1298             return empty();
1299         } else {
1300             return new DistinctIterator<>(this, TreeSet.empty(comparator), Function.identity());
1301         }
1302     }
1303 
1304     @Override
1305     default <U> Iterator<T> distinctBy(Function<? super T, ? extends U> keyExtractor) {
1306         Objects.requireNonNull(keyExtractor, "keyExtractor is null");
1307         if (!hasNext()) {
1308             return empty();
1309         } else {
1310             return new DistinctIterator<>(this, io.vavr.collection.HashSet.empty(), keyExtractor);
1311         }
1312     }
1313 
1314     /**
1315      * Removes up to n elements from this iterator.
1316      *
1317      * @param n A number
1318      * @return The empty iterator, if {@code n <= 0} or this is empty, otherwise a new iterator without the first n elements.
1319      */
1320     @Override
1321     default Iterator<T> drop(int n) {
1322         if (n <= 0) {
1323             return this;
1324         } else if (!hasNext()) {
1325             return empty();
1326         } else {
1327             final Iterator<T> that = this;
1328             return new AbstractIterator<T>() {
1329 
1330                 long count = n;
1331 
1332                 @Override
1333                 public boolean hasNext() {
1334                     while (count > 0 && that.hasNext()) {
1335                         that.next(); // discarded
1336                         count--;
1337                     }
1338                     return that.hasNext();
1339                 }
1340 
1341                 @Override
1342                 public T getNext() {
1343                     return that.next();
1344                 }
1345             };
1346         }
1347     }
1348 
1349     @Override
1350     default Iterator<T> dropRight(int n) {
1351         if (n <= 0) {
1352             return this;
1353         } else if (!hasNext()) {
1354             return empty();
1355         } else {
1356             final Iterator<T> that = this;
1357             return new AbstractIterator<T>() {
1358                 private io.vavr.collection.Queue<T> queue = io.vavr.collection.Queue.empty();
1359 
1360                 @Override
1361                 public boolean hasNext() {
1362                     while (queue.length() < n && that.hasNext()) {
1363                         queue = queue.append(that.next());
1364                     }
1365                     return queue.length() == n && that.hasNext();
1366                 }
1367 
1368                 @Override
1369                 public T getNext() {
1370                     final Tuple2<T, io.vavr.collection.Queue<T>> t = queue.append(that.next()).dequeue();
1371                     queue = t._2;
1372                     return t._1;
1373                 }
1374             };
1375         }
1376     }
1377 
1378     @Override
1379     default Iterator<T> dropUntil(Predicate<? super T> predicate) {
1380         Objects.requireNonNull(predicate, "predicate is null");
1381         return dropWhile(predicate.negate());
1382     }
1383 
1384     @Override
1385     default Iterator<T> dropWhile(Predicate<? super T> predicate) {
1386         Objects.requireNonNull(predicate, "predicate is null");
1387         if (!hasNext()) {
1388             return empty();
1389         } else {
1390             final Iterator<T> that = this;
1391             return new AbstractIterator<T>() {
1392 
1393                 private T next;
1394                 private boolean cached = false;
1395                 private boolean first = true;
1396 
1397                 @Override
1398                 public boolean hasNext() {
1399                     if (cached) {
1400                         return true;
1401                     } else if (first) {
1402                         first = false;
1403                         while (that.hasNext()) {
1404                             next = that.next();
1405                             if (!predicate.test(next)) {
1406                                 cached = true;
1407                                 return true;
1408                             }
1409                         }
1410                         return false;
1411                     } else if (that.hasNext()) {
1412                         next = that.next();
1413                         cached = true;
1414                         return true;
1415                     } else {
1416                         return false;
1417                     }
1418                 }
1419 
1420                 @Override
1421                 public T getNext() {
1422                     cached = false;
1423                     return next;
1424                 }
1425             };
1426         }
1427     }
1428 
1429     /**
1430      * Returns an Iterator that contains elements that satisfy the given {@code predicate}.
1431      *
1432      * @param predicate A predicate
1433      * @return A new Iterator
1434      */
1435     @Override
1436     default Iterator<T> filter(Predicate<? super T> predicate) {
1437         Objects.requireNonNull(predicate, "predicate is null");
1438         if (!hasNext()) {
1439             return empty();
1440         } else {
1441             final Iterator<T> that = this;
1442             return new AbstractIterator<T>() {
1443 
1444                 Option<T> next = Option.none();
1445 
1446                 @Override
1447                 public boolean hasNext() {
1448                     while (next.isEmpty() && that.hasNext()) {
1449                         final T candidate = that.next();
1450                         if (predicate.test(candidate)) {
1451                             next = Option.some(candidate);
1452                         }
1453                     }
1454                     return next.isDefined();
1455                 }
1456 
1457                 @Override
1458                 public T getNext() {
1459                     final T result = next.get();
1460                     next = Option.none();
1461                     return result;
1462                 }
1463             };
1464         }
1465     }
1466 
1467     @Override
1468     default Option<T> findLast(Predicate<? super T> predicate) {
1469         Objects.requireNonNull(predicate, "predicate is null");
1470         T last = null;
1471         while (hasNext()) {
1472             final T elem = next();
1473             if (predicate.test(elem)) {
1474                 last = elem;
1475             }
1476         }
1477         return Option.of(last);
1478     }
1479 
1480     /**
1481      * FlatMaps the elements of this Iterator to Iterables, which are iterated in the order of occurrence.
1482      *
1483      * @param mapper A mapper
1484      * @param <U>    Component type
1485      * @return A new Iterable
1486      */
1487     @Override
1488     default <U> Iterator<U> flatMap(Function<? super T, ? extends Iterable<? extends U>> mapper) {
1489         Objects.requireNonNull(mapper, "mapper is null");
1490         if (!hasNext()) {
1491             return empty();
1492         } else {
1493             final Iterator<T> that = this;
1494             return new AbstractIterator<U>() {
1495 
1496                 final Iterator<? extends T> inputs = that;
1497                 java.util.Iterator<? extends U> current = java.util.Collections.emptyIterator();
1498 
1499                 @Override
1500                 public boolean hasNext() {
1501                     boolean currentHasNext;
1502                     while (!(currentHasNext = current.hasNext()) && inputs.hasNext()) {
1503                         current = mapper.apply(inputs.next()).iterator();
1504                     }
1505                     return currentHasNext;
1506                 }
1507 
1508                 @Override
1509                 public U getNext() {
1510                     return current.next();
1511                 }
1512             };
1513         }
1514     }
1515 
1516     @Override
1517     default <U> U foldRight(U zero, BiFunction<? super T, ? super U, ? extends U> f) {
1518         Objects.requireNonNull(f, "f is null");
1519         return Stream.ofAll(this).foldRight(zero, f);
1520     }
1521 
1522     @Override
1523     default T get() {
1524         return head();
1525     }
1526 
1527     @Override
1528     default <C> Map<C, Iterator<T>> groupBy(Function<? super T, ? extends C> classifier) {
1529         return io.vavr.collection.Collections.groupBy(this, classifier, Iterator::ofAll);
1530     }
1531 
1532     @Override
1533     default Iterator<Seq<T>> grouped(int size) {
1534         return new GroupedIterator<>(this, size, size);
1535     }
1536     
1537     @Override
1538     default boolean hasDefiniteSize() {
1539         return false;
1540     }
1541 
1542     @Override
1543     default T head() {
1544         if (!hasNext()) {
1545             throw new NoSuchElementException("head() on empty iterator");
1546         }
1547         return next();
1548     }
1549 
1550     @Override
1551     default Iterator<T> init() {
1552         if (!hasNext()) {
1553             throw new UnsupportedOperationException();
1554         } else {
1555             return dropRight(1);
1556         }
1557     }
1558 
1559     @Override
1560     default Option<Iterator<T>> initOption() {
1561         return hasNext() ? Option.some(init()) : Option.none();
1562     }
1563 
1564     /**
1565      * An {@code Iterator} is computed synchronously.
1566      *
1567      * @return false
1568      */
1569     @Override
1570     default boolean isAsync() {
1571         return false;
1572     }
1573 
1574     @Override
1575     default boolean isEmpty() {
1576         return !hasNext();
1577     }
1578 
1579     /**
1580      * An {@code Iterator} is computed lazily.
1581      *
1582      * @return true
1583      */
1584     @Override
1585     default boolean isLazy() {
1586         return true;
1587     }
1588 
1589     @Override
1590     default boolean isTraversableAgain() {
1591         return false;
1592     }
1593 
1594     @Override
1595     default boolean isSequential() {
1596         return true;
1597     }
1598 
1599     @Override
1600     default Iterator<T> iterator() {
1601         return this;
1602     }
1603 
1604     @Override
1605     default int length() {
1606         return foldLeft(0, (n, ignored) -> n + 1);
1607     }
1608 
1609     /**
1610      * Maps the elements of this Iterator lazily using the given {@code mapper}.
1611      *
1612      * @param mapper A mapper.
1613      * @param <U>    Component type
1614      * @return A new Iterator
1615      */
1616     @Override
1617     default <U> Iterator<U> map(Function<? super T, ? extends U> mapper) {
1618         Objects.requireNonNull(mapper, "mapper is null");
1619         if (!hasNext()) {
1620             return empty();
1621         } else {
1622             final Iterator<T> that = this;
1623             return new AbstractIterator<U>() {
1624 
1625                 @Override
1626                 public boolean hasNext() {
1627                     return that.hasNext();
1628                 }
1629 
1630                 @Override
1631                 public U getNext() {
1632                     return mapper.apply(that.next());
1633                 }
1634             };
1635         }
1636     }
1637 
1638     @Override
1639     default Iterator<T> orElse(Iterable<? extends T> other) {
1640         return isEmpty() ? ofAll(other) : this;
1641     }
1642 
1643     @Override
1644     default Iterator<T> orElse(Supplier<? extends Iterable<? extends T>> supplier) {
1645         return isEmpty() ? ofAll(supplier.get()) : this;
1646     }
1647 
1648     @Override
1649     default Tuple2<Iterator<T>, Iterator<T>> partition(Predicate<? super T> predicate) {
1650         Objects.requireNonNull(predicate, "predicate is null");
1651         if (!hasNext()) {
1652             return Tuple.of(empty(), empty());
1653         } else {
1654             final Stream<T> that = Stream.ofAll(this);
1655             final Iterator<T> first = that.iterator().filter(predicate);
1656             final Iterator<T> second = that.iterator().filter(predicate.negate());
1657             return Tuple.of(first, second);
1658         }
1659     }
1660 
1661     @Override
1662     default Iterator<T> peek(Consumer<? super T> action) {
1663         Objects.requireNonNull(action, "action is null");
1664         if (!hasNext()) {
1665             return empty();
1666         } else {
1667             final Iterator<T> that = this;
1668             return new AbstractIterator<T>() {
1669                 @Override
1670                 public boolean hasNext() {
1671                     return that.hasNext();
1672                 }
1673 
1674                 @Override
1675                 public T getNext() {
1676                     final T next = that.next();
1677                     action.accept(next);
1678                     return next;
1679                 }
1680             };
1681         }
1682     }
1683 
1684     @Override
1685     default T reduceLeft(BiFunction<? super T, ? super T, ? extends T> op) {
1686         Objects.requireNonNull(op, "op is null");
1687         if (isEmpty()) {
1688             throw new NoSuchElementException("reduceLeft on Nil");
1689         } else {
1690             final Stream<T> stream = Stream.ofAll(this);
1691             return stream.tail().foldLeft(stream.head(), op);
1692         }
1693     }
1694 
1695     @Override
1696     default T reduceRight(BiFunction<? super T, ? super T, ? extends T> op) {
1697         Objects.requireNonNull(op, "op is null");
1698         if (isEmpty()) {
1699             throw new NoSuchElementException("reduceRight on Nil");
1700         } else {
1701             final Stream<T> reversed = Stream.ofAll(this).reverse();
1702             return reversed.reduceLeft((xs, x) -> op.apply(x, xs));
1703         }
1704     }
1705 
1706     @Override
1707     default Iterator<T> replace(T currentElement, T newElement) {
1708         if (!hasNext()) {
1709             return empty();
1710         } else {
1711             final Iterator<T> that = this;
1712             return new AbstractIterator<T>() {
1713                 boolean isFirst = true;
1714 
1715                 @Override
1716                 public boolean hasNext() {
1717                     return that.hasNext();
1718                 }
1719 
1720                 @Override
1721                 public T getNext() {
1722                     final T elem = that.next();
1723                     if (isFirst && Objects.equals(currentElement, elem)) {
1724                         isFirst = false;
1725                         return newElement;
1726                     } else {
1727                         return elem;
1728                     }
1729                 }
1730             };
1731         }
1732     }
1733 
1734     @Override
1735     default Iterator<T> replaceAll(T currentElement, T newElement) {
1736         if (!hasNext()) {
1737             return empty();
1738         } else {
1739             final Iterator<T> that = this;
1740             return new AbstractIterator<T>() {
1741 
1742                 @Override
1743                 public boolean hasNext() {
1744                     return that.hasNext();
1745                 }
1746 
1747                 @Override
1748                 public T getNext() {
1749                     final T elem = that.next();
1750                     if (Objects.equals(currentElement, elem)) {
1751                         return newElement;
1752                     } else {
1753                         return elem;
1754                     }
1755                 }
1756             };
1757         }
1758     }
1759 
1760     @Override
1761     default Iterator<T> retainAll(Iterable<? extends T> elements) {
1762         return io.vavr.collection.Collections.retainAll(this, elements);
1763     }
1764 
1765     @Override
1766     default Traversable<T> scan(T zero, BiFunction<? super T, ? super T, ? extends T> operation) {
1767         return scanLeft(zero, operation);
1768     }
1769 
1770     @Override
1771     default <U> Iterator<U> scanLeft(U zero, BiFunction<? super U, ? super T, ? extends U> operation) {
1772         Objects.requireNonNull(operation, "operation is null");
1773         if (isEmpty()) {
1774             return of(zero);
1775         } else {
1776             final Iterator<T> that = this;
1777             return new AbstractIterator<U>() {
1778 
1779                 boolean isFirst = true;
1780                 U acc = zero;
1781 
1782                 @Override
1783                 public boolean hasNext() {
1784                     return isFirst || that.hasNext();
1785                 }
1786 
1787                 @Override
1788                 public U getNext() {
1789                     if (isFirst) {
1790                         isFirst = false;
1791                         return acc;
1792                     } else {
1793                         acc = operation.apply(acc, that.next());
1794                         return acc;
1795                     }
1796                 }
1797             };
1798         }
1799     }
1800 
1801     // not lazy!
1802     @Override
1803     default <U> Iterator<U> scanRight(U zero, BiFunction<? super T, ? super U, ? extends U> operation) {
1804         Objects.requireNonNull(operation, "operation is null");
1805         if (isEmpty()) {
1806             return of(zero);
1807         } else {
1808             return io.vavr.collection.Collections.scanRight(this, zero, operation, Function.identity());
1809         }
1810     }
1811 
1812     @Override
1813     default Iterator<Seq<T>> slideBy(Function<? super T, ?> classifier) {
1814         Objects.requireNonNull(classifier, "classifier is null");
1815         if (!hasNext()) {
1816             return empty();
1817         } else {
1818             final Stream<T> source = Stream.ofAll(this);
1819             return new AbstractIterator<Seq<T>>() {
1820                 private Stream<T> that = source;
1821                 private Stream<T> next = null;
1822 
1823                 @Override
1824                 public boolean hasNext() {
1825                     while (next == null && !that.isEmpty()) {
1826                         final Object key = classifier.apply(that.head());
1827                         final Tuple2<Stream<T>, Stream<T>> split = that.splitAt(e -> !key.equals(classifier.apply(e)));
1828                         next = split._1;
1829                         that = split._2;
1830                     }
1831                     return next != null;
1832                 }
1833 
1834                 @Override
1835                 public Stream<T> getNext() {
1836                     final Stream<T> result = next;
1837                     next = null;
1838                     return result;
1839                 }
1840             };
1841         }
1842     }
1843 
1844     @Override
1845     default Iterator<Seq<T>> sliding(int size) {
1846         return sliding(size, 1);
1847     }
1848 
1849     @Override
1850     default Iterator<Seq<T>> sliding(int size, int step) {
1851         return new GroupedIterator<>(this, size, step);
1852     }
1853     
1854     @Override
1855     default Tuple2<Iterator<T>, Iterator<T>> span(Predicate<? super T> predicate) {
1856         Objects.requireNonNull(predicate, "predicate is null");
1857         if (!hasNext()) {
1858             return Tuple.of(empty(), empty());
1859         } else {
1860             final Stream<T> that = Stream.ofAll(this);
1861             return Tuple.of(that.iterator().takeWhile(predicate), that.iterator().dropWhile(predicate));
1862         }
1863     }
1864 
1865     @Override
1866     default String stringPrefix() {
1867         return "Iterator";
1868     }
1869 
1870     @Override
1871     default Iterator<T> tail() {
1872         if (!hasNext()) {
1873             throw new UnsupportedOperationException();
1874         } else {
1875             next(); // remove first element
1876             return this;
1877         }
1878     }
1879 
1880     @Override
1881     default Option<Iterator<T>> tailOption() {
1882         if (hasNext()) {
1883             next();
1884             return Option.some(this);
1885         } else {
1886             return Option.none();
1887         }
1888     }
1889 
1890     /**
1891      * Take the first n elements from this iterator.
1892      *
1893      * @param n A number
1894      * @return The empty iterator, if {@code n <= 0} or this is empty, otherwise a new iterator without the first n elements.
1895      */
1896     @Override
1897     default Iterator<T> take(int n) {
1898         if (n <= 0 || !hasNext()) {
1899             return empty();
1900         } else {
1901             final Iterator<T> that = this;
1902             return new AbstractIterator<T>() {
1903 
1904                 long count = n;
1905 
1906                 @Override
1907                 public boolean hasNext() {
1908                     return count > 0 && that.hasNext();
1909                 }
1910 
1911                 @Override
1912                 public T getNext() {
1913                     count--;
1914                     return that.next();
1915                 }
1916             };
1917         }
1918     }
1919 
1920     @Override
1921     default Iterator<T> takeRight(int n) {
1922         if (n <= 0) {
1923             return empty();
1924         } else {
1925             final Iterator<T> that = this;
1926             return new AbstractIterator<T>() {
1927                 private io.vavr.collection.Queue<T> queue = io.vavr.collection.Queue.empty();
1928 
1929                 @Override
1930                 public boolean hasNext() {
1931                     while (that.hasNext()) {
1932                         queue = queue.enqueue(that.next());
1933                         if (queue.length() > n) {
1934                             queue = queue.dequeue()._2;
1935                         }
1936                     }
1937                     return queue.length() > 0;
1938                 }
1939 
1940                 @Override
1941                 public T getNext() {
1942                     final Tuple2<T, io.vavr.collection.Queue<T>> t = queue.dequeue();
1943                     queue = t._2;
1944                     return t._1;
1945                 }
1946             };
1947         }
1948     }
1949 
1950     @Override
1951     default Iterator<T> takeUntil(Predicate<? super T> predicate) {
1952         Objects.requireNonNull(predicate, "predicate is null");
1953         return takeWhile(predicate.negate());
1954     }
1955 
1956     @Override
1957     default Iterator<T> takeWhile(Predicate<? super T> predicate) {
1958         Objects.requireNonNull(predicate, "predicate is null");
1959         if (!hasNext()) {
1960             return empty();
1961         } else {
1962             final Iterator<T> that = this;
1963             return new AbstractIterator<T>() {
1964 
1965                 private T next;
1966                 private boolean cached = false;
1967                 private boolean finished = false;
1968 
1969                 @Override
1970                 public boolean hasNext() {
1971                     if (cached) {
1972                         return true;
1973                     } else if (finished) {
1974                         return false;
1975                     } else if (that.hasNext()) {
1976                         next = that.next();
1977                         if (predicate.test(next)) {
1978                             cached = true;
1979                             return true;
1980                         }
1981                     }
1982                     finished = true;
1983                     return false;
1984                 }
1985 
1986                 @Override
1987                 public T getNext() {
1988                     cached = false;
1989                     return next;
1990                 }
1991             };
1992         }
1993     }
1994 }
1995 
1996 interface IteratorModule {
1997 
1998     final class ConcatIterator<T> extends AbstractIterator<T> {
1999 
2000         private final Iterator<? extends Iterator<? extends T>> iterators;
2001         private Iterator<? extends T> current = Iterator.empty();
2002 
2003         ConcatIterator(Iterator<? extends Iterator<? extends T>> iterators) {
2004             this.iterators = iterators;
2005         }
2006 
2007         @Override
2008         public boolean hasNext() {
2009             while (!current.hasNext() && !iterators.isEmpty()) {
2010                 current = iterators.next();
2011             }
2012             return current.hasNext();
2013         }
2014 
2015         @Override
2016         public T getNext() {
2017             return current.next();
2018         }
2019     }
2020 
2021     final class DistinctIterator<T, U> extends AbstractIterator<T> {
2022 
2023         private final Iterator<? extends T> that;
2024         private io.vavr.collection.Set<U> known;
2025         private final Function<? super T, ? extends U> keyExtractor;
2026         private T next = null;
2027 
2028         DistinctIterator(Iterator<? extends T> that, io.vavr.collection.Set<U> set, Function<? super T, ? extends U> keyExtractor) {
2029             this.that = that;
2030             this.known = set;
2031             this.keyExtractor = keyExtractor;
2032         }
2033 
2034         @Override
2035         public boolean hasNext() {
2036             while (next == null && that.hasNext()) {
2037                 final T elem = that.next();
2038                 final U key = keyExtractor.apply(elem);
2039                 if (!known.contains(key)) {
2040                     known = known.add(key);
2041                     next = elem;
2042                 }
2043             }
2044             return next != null;
2045         }
2046 
2047         @Override
2048         public T getNext() {
2049             final T result = next;
2050             next = null;
2051             return result;
2052         }
2053     }
2054 
2055     final class EmptyIterator implements Iterator<Object> {
2056 
2057         static final EmptyIterator INSTANCE = new EmptyIterator();
2058 
2059         @Override
2060         public boolean hasNext() { return false; }
2061 
2062         @Override
2063         public Object next() { throw new NoSuchElementException(stringPrefix() + ".next()"); }
2064 
2065         @Override
2066         public String stringPrefix() {
2067             return "EmptyIterator";
2068         }
2069 
2070         @Override
2071         public String toString() {
2072             return stringPrefix() + "()";
2073         }
2074     }
2075 
2076     final class GroupedIterator<T> implements Iterator<Seq<T>> {
2077 
2078         private final Iterator<T> that;
2079         private final int size;
2080         private final int step;
2081         private final int gap;
2082         private final int preserve;
2083 
2084         private Object[] buffer;
2085 
2086         GroupedIterator(Iterator<T> that, int size, int step) {
2087             if (size < 1 || step < 1) {
2088                 throw new IllegalArgumentException("size (" + size + ") and step (" + step + ") must both be positive");
2089             }
2090             this.that = that;
2091             this.size = size;
2092             this.step = step;
2093             this.gap = Math.max(step - size, 0);
2094             this.preserve = Math.max(size - step, 0);
2095             this.buffer = take(that, new Object[size], 0, size);
2096         }
2097 
2098         @Override
2099         public boolean hasNext() {
2100             return buffer.length > 0;
2101         }
2102 
2103         @Override
2104         public Seq<T> next() {
2105             if (buffer.length == 0) {
2106                 throw new NoSuchElementException();
2107             }
2108             final Object[] result = buffer;
2109             if (that.hasNext()) {
2110                 buffer = new Object[size];
2111                 if (preserve > 0) {
2112                     System.arraycopy(result, step, buffer, 0, preserve);
2113                 }
2114                 if (gap > 0) {
2115                     drop(that, gap);
2116                     buffer = take(that, buffer, preserve, size);
2117                 } else {
2118                     buffer = take(that, buffer, preserve, step);
2119                 }
2120             } else {
2121                 buffer = new Object[0];
2122             }
2123             return Array.wrap(result);
2124         }
2125 
2126         private static void drop(Iterator<?> source, int count) {
2127             for (int i = 0; i < count && source.hasNext(); i++) {
2128                 source.next();
2129             }
2130         }
2131 
2132         private static Object[] take(Iterator<?> source, Object[] target, int offset, int count) {
2133             int i = offset;
2134             while (i < count + offset && source.hasNext()) {
2135                 target[i] = source.next();
2136                 i++;
2137             }
2138             if (i < target.length) {
2139                 final Object[] result = new Object[i];
2140                 System.arraycopy(target, 0, result, 0, i);
2141                 return result;
2142             } else {
2143                 return target;
2144             }
2145         }
2146     }
2147 
2148     final class BigDecimalHelper {
2149 
2150         @GwtIncompatible("Math::nextDown is not implemented")
2151         private static final Lazy<BigDecimal> INFINITY_DISTANCE = Lazy.of(() -> {
2152             final BigDecimal two = BigDecimal.valueOf(2);
2153             final BigDecimal supremum = BigDecimal.valueOf(Math.nextDown(Double.POSITIVE_INFINITY));
2154             BigDecimal lowerBound = supremum;
2155             BigDecimal upperBound = two.pow(Double.MAX_EXPONENT + 1);
2156             while (true) {
2157                 final BigDecimal magicValue = lowerBound.add(upperBound).divide(two, HALF_UP);
2158                 if (Double.isInfinite(magicValue.doubleValue())) {
2159                     if (areEqual(magicValue, upperBound)) {
2160                         return magicValue.subtract(supremum);
2161                     }
2162                     upperBound = magicValue;
2163                 } else {
2164                     lowerBound = magicValue;
2165                 }
2166             }
2167         });
2168 
2169         /* scale-independent equality */
2170         static boolean areEqual(BigDecimal from, BigDecimal toExclusive) {
2171             return from.compareTo(toExclusive) == 0;
2172         }
2173 
2174         /* parse infinite values also */
2175         @GwtIncompatible("Math::nextUp is not implemented")
2176         static BigDecimal asDecimal(double number) {
2177             if (number == NEGATIVE_INFINITY) {
2178                 final BigDecimal result = BigDecimal.valueOf(Math.nextUp(NEGATIVE_INFINITY));
2179                 return result.subtract(INFINITY_DISTANCE.get());
2180             } else if (number == POSITIVE_INFINITY) {
2181                 final BigDecimal result = BigDecimal.valueOf(Math.nextDown(POSITIVE_INFINITY));
2182                 return result.add(INFINITY_DISTANCE.get());
2183             } else {
2184                 return BigDecimal.valueOf(number);
2185             }
2186         }
2187     }
2188 }